﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Diagnostics;
using System.IO;
using System.Windows.Media;

namespace Kiosk.Utilities
{
    public class Mapper
    {
        private List<Point> points = new List<Point>();

        /// <summary>
        /// Returns a list of points from the kiosk to the passed in x,y coordinate
        /// </summary>
        public PathGeometry GetPath(int x, int y)
        {
            ProcessStartInfo psi = new ProcessStartInfo("MappingStub.exe");
            //psi.Arguments = string.Format("{0},{1}", x, y);
            psi.Arguments = "random 150";
            psi.RedirectStandardOutput = true;
            psi.WindowStyle = System.Diagnostics.ProcessWindowStyle.Hidden;
            psi.UseShellExecute = false;
            using(Process mappingApp = Process.Start(psi))
            {
                mappingApp.WaitForExit();
                if(mappingApp.HasExited)
                {
                    string output = mappingApp.StandardOutput.ReadToEnd();
                    char[] splitter = { ':' };
                    foreach (string p in output.Split(splitter, StringSplitOptions.RemoveEmptyEntries))
                    {
                        double x1 = double.Parse(p.Split(',')[0]);
                        double y1 = double.Parse(p.Split(',')[1]);
                        points.Add(new Point(x1, y1));
                    }
                }

            }

            PathFigure routePathFigure = new PathFigure();

            // if we have points get our line, else get a line from 0,0 to 0,0
            if (points.Count > 0)
            {
                SimplifyStraightLines();
                routePathFigure.StartPoint = points[0];
                for (int i = 1; i < points.Count; i++)
                {
                    LineSegment myLineSegment = new LineSegment(points[i], true);
                    routePathFigure.Segments.Add(myLineSegment);
                }
            }
            else
            { 
                routePathFigure.StartPoint = new Point(0,0);
                routePathFigure.Segments.Add(new LineSegment(new Point(0,0),true));
            }

            PathGeometry myPathGeometry = new PathGeometry();
            myPathGeometry.Figures.Add(routePathFigure);
            return myPathGeometry;
        }

        private void SimplifyStraightLines()
        { 
            if (points.Count < 2)
                return;

            List<Point> newPath = new List<Point>();
            // we want the first point
            newPath.Add(points[0]);

            double lastSlope = CalcSlope(points[0], points[1]);
            for (int i = 1; i < points.Count; i++ )
            {
                if (points.Count > i + 1)
                {
                    double currentSlope = CalcSlope(points[i], points[i + 1]);
                    if (currentSlope != lastSlope)
                    {
                        newPath.Add(points[i]);
                    }
                    lastSlope = currentSlope;
                }
            }

            newPath.Add(points.Last());

            this.points = newPath;
        }

        private double CalcSlope(Point p1, Point p2)
        {
            double rise = p2.Y - p1.Y;
            double run = p2.X - p1.X;

            // vertical line segment
            if (run == 0)
            {
                return double.MinValue;
            }
            return rise / run;

        }



    }
}
